#include <iostream>
#include <vector>
#include <string>
#include <sstream>
#include <jsoncpp/json/json.h>
#include <memory>

std::string serialize()
{
    // 1. 将需要进行序列化的数据，存储在Json::Value对象中
    Json::Value root;
    root["姓名"] = "李华";
    root["年龄"] = 18;
    /* 认为uroot["分数"]只是一个普通的数据，若使用"="来为数组赋值，则会覆盖前面的数据。数组属性的数据需要使用append */
    root["成绩"].append(98);
    root["成绩"].append(95);
    root["成绩"].append(98.5);
    // 2. 实例化一个StreamWriterBuilder工厂类对象
    Json::StreamWriterBuilder swb;
    // 3. 通过StreamWriterBuilder工厂类对象生产一个StreamWriter对象
    std::unique_ptr<Json::StreamWriter> sw(swb.newStreamWriter());
    // 4. 使用StreamWriter对象对Json::Value中的数据做序列化
    std::stringstream ss;
    int n = sw->write(root, &ss);
    if (n != 0)
    {
        std::cerr << "json serialize failed!" << std::endl;
        return "";
    }
    std::cout << ss.str() << std::endl;

    return ss.str();
}

void unserialize(const std::string str)
{
    // 1. 实例化一个CharReaderBuilder工厂类对象
    Json::CharReaderBuilder crb;
    // 2. 通过CharReaderBuilder工厂类对象生产一个CharReader对象
    std::unique_ptr<Json::CharReader> cr(crb.newCharReader());
    // 3. 实例化一个Json::Value对象用来存储解析出的数据
    Json::Value root;
    // 4. 使用CharReader对象进行json格式字符串str的反序列化
    std::string err;
    bool ret = cr->parse(str.c_str(), str.c_str() + str.size(), &root, &err);
    if(ret == false)
    {
        std::cout << "unserialize failed: " << err << std::endl;
        return ;
    }
    // 5. 逐个元素去访问Json::Value中的数据
    std::cout << "姓名：" << root["姓名"].asString() << std::endl;
    std::cout << "年龄：" << root["年龄"].asInt() << std::endl;
    int num = root["成绩"].size();
    std::cout << "成绩：";
    for(int i = 0; i < num; ++i)
    {
        std::cout << root["成绩"][i].asDouble() << ", ";
    }
    std::cout << std::endl; 
}

int main()
{
    std::string str = serialize();
    unserialize(str);

    return 0;
}